package integration

import (
	"context"
	"fmt"
	"sync"

	"gitee.com/wangshh_123/cross-pay-go/src/config"
	"gitee.com/wangshh_123/cross-pay-go/src/platform/common"
	"gitee.com/wangshh_123/cross-pay-go/src/platform/providers/hlPay"
	"gitee.com/wangshh_123/cross-pay-go/src/platform/providers/photonpay"
	"github.com/gin-gonic/gin"
)

// PlatformFactory 平台工厂接口
type PlatformFactory interface {
	// CreateHandler 创建平台处理器
	CreateHandler(platformID string) (PlatformHandler, error)
	// RegisterHandler 注册平台处理器
	RegisterHandler(platformID string, handler PlatformHandler)
	// GetSupportedPlatforms 获取支持的平台列表
	GetSupportedPlatforms() []string
	// InitializePlatforms 初始化所有平台
	InitializePlatforms(configs map[string]*common.PlatformConfig) error
	// GetPlatformConfig 获取平台配置
	GetPlatformConfig(platformID string) (*common.PlatformConfig, error)
	// InitializeAllPlatforms 初始化所有支持的平台
	InitializeAllPlatforms() error
}

// platformFactory 平台工厂实现
type platformFactory struct {
	handlers map[string]PlatformHandler
	configs  map[string]*common.PlatformConfig
	mu       sync.RWMutex
}

// NewPlatformFactory 创建新的平台工厂
func NewPlatformFactory() PlatformFactory {
	return &platformFactory{
		handlers: make(map[string]PlatformHandler),
		configs:  make(map[string]*common.PlatformConfig),
	}
}

// CreateHandler 创建平台处理器
func (f *platformFactory) CreateHandler(platformID string) (PlatformHandler, error) {
	f.mu.RLock()
	defer f.mu.RUnlock()

	if handler, exists := f.handlers[platformID]; exists {
		return handler, nil
	}
	return nil, fmt.Errorf("platform %s not supported", platformID)
}

// RegisterHandler 注册平台处理器
func (f *platformFactory) RegisterHandler(platformID string, handler PlatformHandler) {
	f.mu.Lock()
	defer f.mu.Unlock()

	f.handlers[platformID] = handler
}

// GetSupportedPlatforms 获取支持的平台列表
func (f *platformFactory) GetSupportedPlatforms() []string {
	f.mu.RLock()
	defer f.mu.RUnlock()

	platforms := make([]string, 0, len(f.handlers))
	for platformID := range f.handlers {
		platforms = append(platforms, platformID)
	}
	return platforms
}

// InitializePlatforms 初始化所有平台
func (f *platformFactory) InitializePlatforms(configs map[string]*common.PlatformConfig) error {
	f.mu.Lock()
	defer f.mu.Unlock()

	// 保存配置
	for platformID, config := range configs {
		f.configs[platformID] = config
	}

	return nil
}

// GetPlatformConfig 获取平台配置
func (f *platformFactory) GetPlatformConfig(platformID string) (*common.PlatformConfig, error) {
	f.mu.RLock()
	defer f.mu.RUnlock()

	if config, exists := f.configs[platformID]; exists {
		return config, nil
	}
	return nil, fmt.Errorf("platform config not found: %s", platformID)
}

// InitializeAllPlatforms 初始化所有支持的平台
func (f *platformFactory) InitializeAllPlatforms() error {
	f.mu.Lock()
	defer f.mu.Unlock()

	// 获取配置
	cfg := config.GetConfig()

	// 初始化 HlPay 平台
	if err := f.initializeHlPayPlatform(cfg); err != nil {
		return fmt.Errorf("failed to initialize HlPay platform: %w", err)
	}

	// 初始化 PhotonPay 平台
	if err := f.initializePhotonPayPlatform(cfg); err != nil {
		return fmt.Errorf("failed to initialize PhotonPay platform: %w", err)
	}

	return nil
}

// initializeHlPayPlatform 初始化HlPay平台
func (f *platformFactory) initializeHlPayPlatform(cfg *config.Config) error {
	// 创建HlPay配置
	hlpayConfig := &common.PlatformConfig{
		AppID:      cfg.HlPay.ClientID,
		AppSecret:  cfg.HlPay.ClientSecret,
		GatewayURL: cfg.HlPay.GatewayURL,
		Timeout:    30,
	}

	// 保存配置
	f.configs["hlpay"] = hlpayConfig

	// 创建HlPay处理器
	handler, err := f.createHlPayHandler(hlpayConfig)
	if err != nil {
		return err
	}

	// 注册处理器
	f.handlers["hlpay"] = handler

	return nil
}

// initializePhotonPayPlatform 初始化PhotonPay平台
func (f *platformFactory) initializePhotonPayPlatform(cfg *config.Config) error {
	// 创建PhotonPay配置
	photonpayConfig := &common.PlatformConfig{
		AppID:      cfg.PhotonPay.AppID,
		AppSecret:  cfg.PhotonPay.AppSecret,
		GatewayURL: cfg.PhotonPay.GatewayURL,
		Timeout:    30,
	}

	// 保存配置
	f.configs["photonpay"] = photonpayConfig

	// 创建PhotonPay处理器
	handler, err := f.createPhotonPayHandler(photonpayConfig)
	if err != nil {
		return err
	}

	// 注册处理器
	f.handlers["photonpay"] = handler

	return nil
}

// createHlPayHandler 创建HlPay处理器
func (f *platformFactory) createHlPayHandler(config *common.PlatformConfig) (PlatformHandler, error) {
	// 转换配置格式
	hlpayConfig := &hlPay.HlPayConfig{
		ClientID:     config.AppID,
		ClientSecret: config.AppSecret,
		GatewayURL:   config.GatewayURL,
		RefreshTime:  int(config.Timeout),
	}

	// 创建HlPay客户端
	hlpayClient := hlPay.GetHlPayClient(hlpayConfig)

	// 创建HlPay适配器处理器
	handler := NewHlPayAdapterHandler("hlpay", config, hlpayClient)

	return handler, nil
}

// createPhotonPayHandler 创建PhotonPay处理器
func (f *platformFactory) createPhotonPayHandler(config *common.PlatformConfig) (PlatformHandler, error) {
	// 转换配置格式
	photonpayConfig := &common.PlatformConfig{
		AppID:      config.AppID,
		AppSecret:  config.AppSecret,
		GatewayURL: config.GatewayURL,
		Timeout:    config.Timeout,
	}

	// 创建PhotonPay客户端
	photonpayClient := photonpay.GetPhotonPayClient(photonpayConfig)

	// 创建PhotonPay适配器处理器
	handler := NewPhotonPayAdapterHandler("photonpay", config, photonpayClient)

	return handler, nil
}

// PlatformManager 平台管理器，提供高级管理功能
type PlatformManager struct {
	factory PlatformFactory
}

// NewPlatformManager 创建平台管理器
func NewPlatformManager() *PlatformManager {
	return &PlatformManager{
		factory: NewPlatformFactory(),
	}
}

// NewPlatformManagerWithClients 创建带有客户端的平台管理器
func NewPlatformManagerWithClients(photonpayClient *photonpay.PhotonPayClient, hlpayClient *hlPay.HlPayClient) *PlatformManager {
	manager := &PlatformManager{
		factory: NewPlatformFactory(),
	}

	// 获取实际配置
	cfg := config.GetConfig()

	// 初始化平台配置
	configs := map[string]*common.PlatformConfig{
		"photonpay": {
			AppID:      cfg.PhotonPay.AppID,
			AppSecret:  cfg.PhotonPay.AppSecret,
			GatewayURL: cfg.PhotonPay.GatewayURL,
			Timeout:    30,
		},
		"hlpay": {
			AppID:      cfg.HlPay.ClientID,
			AppSecret:  cfg.HlPay.ClientSecret,
			GatewayURL: cfg.HlPay.GatewayURL,
			Timeout:    30,
		},
	}

	// 初始化平台
	manager.InitializeWithConfig(configs)

	// 手动注册处理器，使用传入的客户端
	if hlpayClient != nil {
		hlpayHandler := NewHlPayAdapterHandler("hlpay", configs["hlpay"], hlpayClient)
		manager.factory.RegisterHandler("hlpay", hlpayHandler)
	}

	if photonpayClient != nil {
		photonpayHandler := NewPhotonPayAdapterHandler("photonpay", configs["photonpay"], photonpayClient)
		manager.factory.RegisterHandler("photonpay", photonpayHandler)
	}

	return manager
}

// GetFactory 获取工厂实例
func (m *PlatformManager) GetFactory() PlatformFactory {
	return m.factory
}

// GetPhotonPayClient 获取PhotonPay客户端
func (m *PlatformManager) GetPhotonPayClient() (*photonpay.PhotonPayClient, error) {
	// 获取PhotonPay配置
	config, err := m.factory.GetPlatformConfig("photonpay")
	if err != nil {
		return nil, fmt.Errorf("photonpay config not found: %w", err)
	}

	// 创建PhotonPay客户端
	photonpayClient := photonpay.GetPhotonPayClient(config)
	return photonpayClient, nil
}

// GetHlPayClient 获取HlPay客户端
func (m *PlatformManager) GetHlPayClient() (*hlPay.HlPayClient, error) {
	// 获取HlPay配置
	config, err := m.factory.GetPlatformConfig("hlpay")
	if err != nil {
		return nil, fmt.Errorf("hlpay config not found: %w", err)
	}

	// 创建HlPay配置
	hlpayConfig := &hlPay.HlPayConfig{
		ClientID:     config.AppID,
		ClientSecret: config.AppSecret,
		GatewayURL:   config.GatewayURL,
		RefreshTime:  int(config.Timeout),
	}

	// 创建HlPay客户端
	hlpayClient := hlPay.GetHlPayClient(hlpayConfig)
	return hlpayClient, nil
}

// InitializeWithConfig 使用配置文件初始化平台
func (m *PlatformManager) InitializeWithConfig(configs map[string]*common.PlatformConfig) error {
	// 初始化平台配置
	if err := m.factory.InitializePlatforms(configs); err != nil {
		return fmt.Errorf("failed to initialize platforms: %w", err)
	}

	return nil
}

// InitializeAllPlatforms 初始化所有平台
func (m *PlatformManager) InitializeAllPlatforms() error {
	return m.factory.InitializeAllPlatforms()
}

// HandleRequest 处理平台请求
func (m *PlatformManager) HandleRequest(ctx context.Context, platformID string, requestType string, request interface{}) (interface{}, error) {
	// 获取平台处理器
	handler, err := m.factory.CreateHandler(platformID)
	if err != nil {
		return nil, err
	}

	// 根据请求类型分发处理
	switch requestType {
	case "card_list":
		if req, ok := request.(*common.CardListRequest); ok {
			return handler.HandleCardList(ctx, req)
		}
		return nil, fmt.Errorf("invalid request type for card_list")
	case "card_bin_list":
		if req, ok := request.(*common.CardBinListRequest); ok {
			return handler.HandleCardBinList(ctx, req)
		}
		return nil, fmt.Errorf("invalid request type for card_bin_list")
	case "card_cvv":
		if req, ok := request.(*common.CardCVVRequest); ok {
			return handler.HandleCardCVV(ctx, req)
		}
		return nil, fmt.Errorf("invalid request type for card_cvv")
	case "card_detail":
		if req, ok := request.(*common.CardDetailRequest); ok {
			return handler.HandleCardDetail(ctx, req)
		}
		return nil, fmt.Errorf("invalid request type for card_detail")
	case "cardholder_list":
		if req, ok := request.(*common.CardholderListRequest); ok {
			return handler.HandleCardholderList(ctx, req)
		}
		return nil, fmt.Errorf("invalid request type for cardholder_list")
	case "create_cardholder":
		if req, ok := request.(*common.CreateCardholderRequest); ok {
			return handler.HandleCreateCardholder(ctx, req)
		}
		return nil, fmt.Errorf("invalid request type for create_cardholder")
	case "update_cardholder":
		if req, ok := request.(*common.UpdateCardholderRequest); ok {
			return handler.HandleUpdateCardholder(ctx, req)
		}
		return nil, fmt.Errorf("invalid request type for update_cardholder")
	case "card_history_list":
		if req, ok := request.(*common.CardHistoryListRequest); ok {
			return handler.HandleCardHistoryList(ctx, req)
		}
		return nil, fmt.Errorf("invalid request type for card_history_list")
	case "open_card":
		if req, ok := request.(*common.OpenCardRequest); ok {
			return handler.HandleOpenCard(ctx, req)
		}
		return nil, fmt.Errorf("invalid request type for open_card")
	case "recharge_card":
		if req, ok := request.(*common.RechargeCardRequest); ok {
			return handler.HandleRechargeCard(ctx, req)
		}
		return nil, fmt.Errorf("invalid request type for recharge_card")
	case "freeze_card":
		if req, ok := request.(*common.FreezeCardRequest); ok {
			return handler.HandleFreezeCard(ctx, req)
		}
		return nil, fmt.Errorf("invalid request type for freeze_card")
	case "enable_card":
		if req, ok := request.(*common.EnableCardRequest); ok {
			return handler.HandleEnableCard(ctx, req)
		}
		return nil, fmt.Errorf("invalid request type for enable_card")
	case "cancel_card":
		if req, ok := request.(*common.CancelCardRequest); ok {
			return handler.HandleCancelCard(ctx, req)
		}
		return nil, fmt.Errorf("invalid request type for cancel_card")
	case "transaction_list":
		if req, ok := request.(*common.TransactionListRequest); ok {
			return handler.HandleTransactionList(ctx, req)
		}
		return nil, fmt.Errorf("invalid request type for transaction_list")
	case "transaction_detail":
		if req, ok := request.(*common.TransactionDetailRequest); ok {
			return handler.HandleTransactionDetail(ctx, req)
		}
		return nil, fmt.Errorf("invalid request type for transaction_detail")
	case "batch_open_card":
		if req, ok := request.(*common.BatchOpenCardRequest); ok {
			return handler.HandleBatchOpenCard(ctx, req)
		}
		return nil, fmt.Errorf("invalid request type for batch_open_card")
	default:
		return nil, fmt.Errorf("unsupported request type: %s", requestType)
	}
}

// HandleRequestWithGinContext 处理平台请求（使用Gin上下文）
func (m *PlatformManager) HandleRequestWithGinContext(ginCtx *gin.Context, platformID string, requestType string, request interface{}) (interface{}, error) {
	// 创建一个新的上下文，包含Gin上下文中的值
	ctx := context.Background()

	// 从Gin上下文中复制关键值到新的上下文
	if matrixAccountInfo := ginCtx.Value("matrix_account_info"); matrixAccountInfo != nil {
		ctx = context.WithValue(ctx, "matrix_account_info", matrixAccountInfo)
	}

	if platformInfo := ginCtx.Value("platform_info"); platformInfo != nil {
		ctx = context.WithValue(ctx, "platform_info", platformInfo)
	}

	if claims := ginCtx.Value("claims"); claims != nil {
		ctx = context.WithValue(ctx, "claims", claims)
	}

	if userID := ginCtx.Value("user_id"); userID != nil {
		ctx = context.WithValue(ctx, "user_id", userID)
	}

	// 调用原有的HandleRequest方法
	return m.HandleRequest(ctx, platformID, requestType, request)
}

// HandleOpenCard 处理开卡请求
func (m *PlatformManager) HandleOpenCard(ctx context.Context, platformID string, request *common.OpenCardRequest) (*common.OpenCardResponse, error) {
	handler, err := m.factory.CreateHandler(platformID)
	if err != nil {
		return nil, err
	}
	return handler.HandleOpenCard(ctx, request)
}

// HandleRechargeCard 处理卡片充值请求
func (m *PlatformManager) HandleRechargeCard(ctx context.Context, platformID string, request *common.RechargeCardRequest) (*common.RechargeCardResponse, error) {
	handler, err := m.factory.CreateHandler(platformID)
	if err != nil {
		return nil, err
	}
	return handler.HandleRechargeCard(ctx, request)
}

// HandleFreezeCard 处理卡片冻结请求
func (m *PlatformManager) HandleFreezeCard(ctx context.Context, platformID string, request *common.FreezeCardRequest) (*common.FreezeCardResponse, error) {
	handler, err := m.factory.CreateHandler(platformID)
	if err != nil {
		return nil, err
	}
	return handler.HandleFreezeCard(ctx, request)
}

// HandleEnableCard 处理卡片解冻请求
func (m *PlatformManager) HandleEnableCard(ctx context.Context, platformID string, request *common.EnableCardRequest) (*common.EnableCardResponse, error) {
	handler, err := m.factory.CreateHandler(platformID)
	if err != nil {
		return nil, err
	}
	return handler.HandleEnableCard(ctx, request)
}

// HandleCancelCard 处理卡片注销请求
func (m *PlatformManager) HandleCancelCard(ctx context.Context, platformID string, request *common.CancelCardRequest) (*common.CancelCardResponse, error) {
	handler, err := m.factory.CreateHandler(platformID)
	if err != nil {
		return nil, err
	}
	return handler.HandleCancelCard(ctx, request)
}

// HandleBatchOpenCard 处理批量开卡请求
func (m *PlatformManager) HandleBatchOpenCard(ctx context.Context, platformID string, request *common.BatchOpenCardRequest) (*common.BatchOpenCardResponse, error) {
	handler, err := m.factory.CreateHandler(platformID)
	if err != nil {
		return nil, err
	}
	return handler.HandleBatchOpenCard(ctx, request)
}

// HandleWithdrawCard 处理卡片提现请求
func (m *PlatformManager) HandleWithdrawCard(ctx context.Context, platformID string, request *common.WithdrawCardRequest) (*common.WithdrawCardResponse, error) {
	handler, err := m.factory.CreateHandler(platformID)
	if err != nil {
		return nil, err
	}
	return handler.HandleWithdrawCard(ctx, request)
}

// GetPlatformInfo 获取平台信息
func (m *PlatformManager) GetPlatformInfo(platformID string) (map[string]interface{}, error) {
	handler, err := m.factory.CreateHandler(platformID)
	if err != nil {
		return nil, err
	}

	config := handler.GetPlatformConfig()

	info := map[string]interface{}{
		"platform_id": handler.GetPlatformID(),
		"config": map[string]interface{}{
			"app_id":      config.AppID,
			"gateway_url": config.GatewayURL,
			"timeout":     config.Timeout,
		},
		"supported_operations": []string{
			"card_list", "card_bin_list", "card_cvv", "card_detail", "cardholder_list", "create_cardholder", "update_cardholder", "card_history_list", "open_card", "recharge_card", "freeze_card", "enable_card", "cancel_card", "transaction_list", "transaction_detail", "batch_open_card",
		},
	}

	return info, nil
}

// ValidatePlatformConfig 验证平台配置
func (m *PlatformManager) ValidatePlatformConfig(config *common.PlatformConfig) error {
	if config == nil {
		return fmt.Errorf("platform config is nil")
	}

	if config.AppID == "" {
		return fmt.Errorf("app_id is required")
	}

	if config.AppSecret == "" {
		return fmt.Errorf("app_secret is required")
	}

	if config.GatewayURL == "" {
		return fmt.Errorf("gateway_url is required")
	}

	if config.Timeout <= 0 {
		return fmt.Errorf("timeout must be greater than 0")
	}

	return nil
}

// 全局平台管理器实例
var globalPlatformManager *PlatformManager
var globalPlatformManagerOnce sync.Once

// GetGlobalPlatformManager 获取全局平台管理器实例
func GetGlobalPlatformManager() *PlatformManager {
	globalPlatformManagerOnce.Do(func() {
		globalPlatformManager = NewPlatformManager()
	})
	return globalPlatformManager
}

// InitializeGlobalPlatforms 初始化全局平台
func InitializeGlobalPlatforms(configs map[string]*common.PlatformConfig) error {
	manager := GetGlobalPlatformManager()
	return manager.InitializeWithConfig(configs)
}

// InitializeAllGlobalPlatforms 初始化所有全局平台
func InitializeAllGlobalPlatforms() error {
	manager := GetGlobalPlatformManager()
	return manager.InitializeAllPlatforms()
}
